package com.hd.quartz.job.task.batch.config;

import com.hd.quartz.job.task.batch.listener.UserSkipListener;
import com.hd.quartz.job.task.batch.mapper.UserFieldSetMapper;
import com.hd.quartz.job.task.batch.pojo.User;
import com.hd.quartz.job.task.batch.processor.UserItemProcessor;
import com.hd.quartz.job.task.batch.writer.UserWriter;
import org.springframework.batch.core.Job;
import org.springframework.batch.core.Step;
import org.springframework.batch.core.configuration.annotation.JobBuilderFactory;
import org.springframework.batch.core.configuration.annotation.StepBuilderFactory;
import org.springframework.batch.core.launch.support.RunIdIncrementer;
import org.springframework.batch.item.file.FlatFileItemReader;
import org.springframework.batch.item.file.mapping.BeanWrapperFieldSetMapper;
import org.springframework.batch.item.file.mapping.DefaultLineMapper;
import org.springframework.batch.item.file.transform.DelimitedLineTokenizer;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.config.ConfigurableBeanFactory;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Scope;
import org.springframework.core.io.ClassPathResource;

/**
 * <h3>partitionjob</h3>
 * <p>config.DemoJob</p>
 *
 * @author : hduong
 * @version : 1.0
 * @date : 2020-09-15 18:05
 **/
@Configuration
public class DemoJob {

    @Autowired
    private JobBuilderFactory jobBuilderFactory;

    @Autowired
    private StepBuilderFactory stepBuilderFactory;

    @Autowired
    private UserSkipListener userSkipListener;

    @Bean("runDemoJob")
    @Scope(value = ConfigurableBeanFactory.SCOPE_SINGLETON)
    public Job runDemoJob() throws Exception {
        return jobBuilderFactory.get("runDemoJob")
                .incrementer(new RunIdIncrementer())
                .start(demoStep())
                .build();
    }


    @Bean("demoStep")
    public Step demoStep() throws Exception {
        return stepBuilderFactory.get("demoStep")
                .<User, User>chunk(2)
                .reader(flatfileReader())
                .processor(userItemProcessor())
                .writer(userWriter())
                .listener(userSkipListener)
                .build();

    }

    @Bean
    public DelimitedLineTokenizer lineTokenizer() {
        DelimitedLineTokenizer tokenizer = new DelimitedLineTokenizer();
        String[] names = new String[]{"id,name,age"};
        tokenizer.setNames(names);
        tokenizer.setDelimiter(DelimitedLineTokenizer.DELIMITER_COMMA);
        return tokenizer;
    }

    @Bean
    public UserFieldSetMapper userFieldSetMapper() {
        return new UserFieldSetMapper();
    }

    @Bean
    public DefaultLineMapper lineMapper() {
        DefaultLineMapper defaultLineMapper = new DefaultLineMapper();
        defaultLineMapper.setLineTokenizer(lineTokenizer());
        defaultLineMapper.setFieldSetMapper(userFieldSetMapper());
        return defaultLineMapper;
    }


    @Bean
    public FlatFileItemReader<User> flatfileReader() {
        FlatFileItemReader<User> reader = new FlatFileItemReader<User>();
        reader.setResource(new ClassPathResource("user.txt"));
        reader.setLineMapper(new DefaultLineMapper<User>() {{

            setLineTokenizer(new DelimitedLineTokenizer() {{
                setNames(new String[] { "id", "name", "age" });
                setDelimiter(DELIMITER_COMMA);
            }});
            setFieldSetMapper(new BeanWrapperFieldSetMapper<User>() {{
                setTargetType(User.class);
            }});
        }});
        return reader;
    }


    @Bean
    public UserItemProcessor userItemProcessor() {
        return new UserItemProcessor();
    }

    @Bean
    public UserWriter userWriter() {
        return new UserWriter();
    }

}
